package com.gitee.xmhzzz.component.oss.template;

import cn.hutool.core.codec.Base64;
import com.aliyun.oss.ClientException;
import com.aliyun.oss.OSSClient;
import com.aliyun.oss.OSSException;
import com.aliyun.oss.common.utils.IOUtils;
import com.aliyun.oss.model.OSSObject;
import com.gitee.xmhzzz.component.common.enums.ResponseCode;
import com.gitee.xmhzzz.component.common.exception.DefaultBusinessException;
import com.gitee.xmhzzz.component.oss.config.OssConfig;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;

/**
 * @ClassName OssTemplate
 * @Description
 * @Author wzq
 * @Date 2023/7/7 14:36
 * @Version 1.0
 */
public class OssTemplate extends AOssTemplate{

    private static final Logger log = LoggerFactory.getLogger(OssTemplate.class);

    public static final String Picture_Format_PGN = "png";
    public static final String Picture_Format_JPEG = "jpeg";

    private OssConfig ossConfig;

    public OssTemplate(OssConfig ossConfig) {
        this.ossConfig = ossConfig;
    }

    public void createBucket(String bucketName){
        OSSClient ossClient = createOSSClient();
        try {
            // 创建存储空间。
            ossClient.createBucket(bucketName);
        } catch (OSSException oe) {
            log.error("######## 阿里oss服务处理异常:{}",oe.getMessage(),oe);
            DefaultBusinessException.of(ResponseCode.CONNECT_EXCEPTION,"阿里oss服务处理异常:"+oe.getMessage());
        } catch (ClientException ce) {
            log.error("######## 阿里oss客户端处理异常:{}",ce.getMessage(),ce);
            DefaultBusinessException.of(ResponseCode.BUSINESS_EXCEPTION,"阿里oss客户端处理异常:"+ce.getMessage());
        } finally {
            if (ossClient != null) {
                this.shutdown(ossClient);
            }
        }
    }

    /**
     *
     * @param base64Img
     * @return
     */
    public String upLoadBase64(String key,String base64Img) {
        int originalFilenameStartIndex = base64Img.indexOf('/');
        int originalFilenameEndIndex = base64Img.indexOf(';');
        String originalFilename = base64Img.substring(originalFilenameStartIndex+1,originalFilenameEndIndex);
        if (Picture_Format_JPEG.equals(originalFilename)) {
            key += ".jpg";
        }else if (Picture_Format_PGN.equals(originalFilename)) {
            key += ".png";
        }else {
            DefaultBusinessException.of(ResponseCode.BAD_REQUEST,"不支持img、png外的格式");
        }
        // 获取base64的文件
        base64Img = base64Img.split(",")[1];

        byte[] bytesFile = Base64.decode(base64Img);

        upLoadFile(key, bytesFile, ossConfig.getBucketName());

        return key;
    }

    public String upLoadFile(String key, String content){
        return upLoadFile(key,content.getBytes());
    }

    public String upLoadFile(String key, byte[] bytes) {
        return upLoadFile(key, bytes, ossConfig.getBucketName());
    }


    public String upLoadPornFile(String key, byte[] bytes) {
        return upLoadFile(ossConfig.getPornKeyPrefix() + "/" + key, bytes, ossConfig.getBucketName());
    }

    /**
     * 上传文件
     * @param key
     * @param bytes
     * @param bucketName
     * @return
     */
    public String upLoadFile(String key, byte[] bytes, String bucketName) {
        // 创建OSSClient实例
        OSSClient ossClient = createOSSClient();
        try {
            // 上传文件。
            ossClient.putObject(bucketName, key, new ByteArrayInputStream(bytes));
        } catch (OSSException oe) {
            log.error("######## 阿里oss服务处理异常:{}",oe.getMessage(),oe);
            DefaultBusinessException.of(ResponseCode.CONNECT_EXCEPTION,"阿里oss服务处理异常:"+oe.getMessage());
        } catch (ClientException ce) {
            log.error("######## 阿里oss客户端处理异常:{}",ce.getMessage(),ce);
            DefaultBusinessException.of(ResponseCode.BUSINESS_EXCEPTION,"阿里oss客户端处理异常:"+ce.getMessage());
        } finally {
            if (ossClient != null) {
                this.shutdown(ossClient);
            }
        }
        return key;
    }

    public String upLoadFile(String key, InputStream input) {
       return upLoadFile(key,input,ossConfig.getBucketName());
    }


    public String upLoadFile(String key, InputStream input, String bucketName) {
        // 创建OSSClient实例
        OSSClient ossClient = createOSSClient();
        try {
            // 上传文件。
            ossClient.putObject(bucketName, key, input);
        } catch (OSSException oe) {
            log.error("######## 阿里oss服务处理异常:{}",oe.getMessage(),oe);
            DefaultBusinessException.of(ResponseCode.CONNECT_EXCEPTION,"阿里oss服务处理异常:"+oe.getMessage());
        } catch (ClientException ce) {
            log.error("######## 阿里oss客户端处理异常:{}",ce.getMessage(),ce);
            DefaultBusinessException.of(ResponseCode.BUSINESS_EXCEPTION,"阿里oss客户端处理异常:"+ce.getMessage());
        } finally {
            if (ossClient != null) {
                this.shutdown(ossClient);
            }
        }
        return key;
    }

    /**
     * 删除文件
     * @param key
     * @return
     */
    public String deleteFile(String key) {
        // 创建OSSClient实例
        OSSClient ossClient = createOSSClient();
        try {
            // 删除文件。
            String bucket = key.startsWith(ossConfig.getPornKeyPrefix()) ?
                    ossConfig.getPornBucketName() : ossConfig.getBucketName();
            ossClient.deleteObject(bucket, key);
        } catch (OSSException oe) {
            log.error("######## 阿里oss服务处理异常:{}",oe.getMessage(),oe);
            DefaultBusinessException.of(ResponseCode.CONNECT_EXCEPTION,"阿里oss服务处理异常:"+oe.getMessage());
        } catch (ClientException ce) {
            log.error("######## 阿里oss客户端处理异常:{}",ce.getMessage(),ce);
            DefaultBusinessException.of(ResponseCode.BUSINESS_EXCEPTION,"阿里oss客户端处理异常:"+ce.getMessage());
        } finally {
            if (ossClient != null) {
                this.shutdown(ossClient);
            }
        }
        return key;
    }

    /**
     * 下载文件
     * @param key
     * @return
     * @throws IOException
     */
    public byte[] getFile(String key) throws IOException {
        byte[] bytes = null;
        // 创建OSSClient实例
        OSSClient ossClient = createOSSClient();
        try {
            String bucket = key.startsWith(ossConfig.getPornKeyPrefix()) ?
                    ossConfig.getPornBucketName() : ossConfig.getBucketName();
            // 下载文件。
            OSSObject ossObject = ossClient.getObject(bucket, key);
            bytes = IOUtils.readStreamAsByteArray(ossObject.getObjectContent());
        } catch (OSSException oe) {
            log.error("######## 阿里oss服务处理异常:{}",oe.getMessage(),oe);
            DefaultBusinessException.of(ResponseCode.CONNECT_EXCEPTION,"阿里oss服务处理异常:"+oe.getMessage());
        } catch (ClientException ce) {
            log.error("######## 阿里oss客户端处理异常:{}",ce.getMessage(),ce);
            DefaultBusinessException.of(ResponseCode.BUSINESS_EXCEPTION,"阿里oss客户端处理异常:"+ce.getMessage());
        } finally {
            if (ossClient != null) {
                this.shutdown(ossClient);
            }
        }
        return bytes;
    }

    public boolean isExistFile(String key) throws IOException {
        // 创建OSSClient实例
        boolean isExist = false;
        OSSClient ossClient = createOSSClient();
        try {
            // 文件是否存在
            isExist = ossClient.doesObjectExist(ossConfig.getBucketName(), key);
        } catch (OSSException oe) {
            log.error("######## 阿里oss服务处理异常:{}",oe.getMessage(),oe);
            DefaultBusinessException.of(ResponseCode.CONNECT_EXCEPTION,"阿里oss服务处理异常:"+oe.getMessage());
        } catch (ClientException ce) {
            log.error("######## 阿里oss客户端处理异常:{}",ce.getMessage(),ce);
            DefaultBusinessException.of(ResponseCode.BUSINESS_EXCEPTION,"阿里oss客户端处理异常:"+ce.getMessage());
        } finally {
            if (ossClient != null) {
                this.shutdown(ossClient);
            }
        }
        return isExist;
    }


    public String getTempAccessUrl(String key) {
        return this.getUrl() + key;
    }

    public String getUrl() {
        return "https://" + ossConfig.getBucketName() + "." + ossConfig.getEndpoint() + "/";
    }

    @Override
    public OssConfig getOssConfig() {
        return this.ossConfig;
    }
}
